package com.inspur.framework.security.filter;

import java.io.IOException;
import java.io.PrintWriter;
import javax.servlet.FilterChain;
import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import com.alibaba.fastjson.JSONObject;
import com.inspur.common.constant.HttpStatus;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.authentication.UsernamePasswordAuthenticationToken;
import org.springframework.security.web.authentication.WebAuthenticationDetailsSource;
import org.springframework.stereotype.Component;
import org.springframework.web.filter.OncePerRequestFilter;
import com.inspur.common.utils.SecurityUtils;
import com.inspur.common.utils.StringUtils;
import com.inspur.framework.security.LoginUser;
import com.inspur.framework.security.service.TokenService;

/**
 * token过滤器 验证token有效性
 *
 * @author inspur_ict
 */
@Component
public class JwtAuthenticationTokenFilter extends OncePerRequestFilter
{
    @Autowired
    private TokenService tokenService;

    /**
     * 仅支持字母、数字、下划线、空格、逗号（支持多个字段排序）
     */
    public static String SQL_PATTERN = "[a-zA-Z0-9_\\ \\,]+";

    @Override
    protected void doFilterInternal(HttpServletRequest request, HttpServletResponse response, FilterChain chain)
            throws ServletException, IOException
    {
        LoginUser loginUser = tokenService.getLoginUser(request);
        if (StringUtils.isNotNull(loginUser) && StringUtils.isNull(SecurityUtils.getAuthentication()))
        {
            tokenService.verifyToken(loginUser);
            UsernamePasswordAuthenticationToken authenticationToken = new UsernamePasswordAuthenticationToken(loginUser, null, loginUser.getAuthorities());
            authenticationToken.setDetails(new WebAuthenticationDetailsSource().buildDetails(request));
            org.springframework.security.core.context.SecurityContextHolder.getContext().setAuthentication(authenticationToken);
        }

        HttpServletRequest httpServletRequest = (HttpServletRequest) request;
        if("POST".equalsIgnoreCase(httpServletRequest.getMethod())){
            ServletRequest requestWrapper = new BodyReaderHttpServletRequestWrapper(httpServletRequest);
            String body = HttpHelper.getBodyString(requestWrapper);
            if(StringUtils.isNotEmpty(body)) {
                JSONObject json = JSONObject.parseObject(body);
                String sort = json.getString("sort");
                String order = json.getString("order");
                if (StringUtils.isNotEmpty(sort) && StringUtils.isNotEmpty(order)) {
                    if (sort.matches(SQL_PATTERN) && ("DESC".equalsIgnoreCase(order) || "ASC".equalsIgnoreCase(order))) {
                        chain.doFilter(requestWrapper, response);
                    } else {
                        response.setHeader("Access-Control-Allow-Origin", "*");
                        response.setStatus(200);
                        response.setContentType("application/json");
                        response.setCharacterEncoding("utf-8");
                        JSONObject result = new JSONObject();
                        result.put("code", HttpStatus.ERROR);
                        result.put("msg","该排序字段非法!");
                        PrintWriter writer = response.getWriter();
                        writer.write(result.toString());
                        writer.flush();
                        writer.close();
                    }
                } else {
                    chain.doFilter(requestWrapper, response);
                }
            }else{
                chain.doFilter(requestWrapper, response);
            }
        }else{
            chain.doFilter(request, response);
        }
    }
}
